﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data.SqlClient;
using System.Data;
using lite;
using Csla;
using Csla.Data;
using Csla.Core;
using System.Collections.ObjectModel;
using OpenExpressApp.ORM;
using OpenExpressApp.MetaAttribute;
using OpenExpressApp.DB.Utils;
using System.Diagnostics;
using OpenExpressApp.Types;
using System.Collections;
using OpenExpressApp.MetaModel;
using OpenExpressApp.MetaModel.View;

namespace OpenExpressApp.Module.Library
{
    [Serializable]
    public partial class OrgPositionOperations : GBusinessListBase<OrgPositionOperations, OrgPositionOperation>, IUnderlyModelList
    {
        protected override string ConnectionString
        {
            get
            {
                return ConnectionStringNames.OpenExpressApp;
            }
        }

        #region  Factory Methods

        private OrgPositionOperations()
        {
            /* Require use of factory methods */
            AllowNew = true;
        }

        public static OrgPositionOperations GetChild(OrgPosition parent)
        {
            return DataPortal.FetchChild<OrgPositionOperations>(parent);
        }


        public static OrgPositionOperations NewChild()
        {
            return DataPortal.CreateChild<OrgPositionOperations>();
        }

        protected override object AddNewCore()
        {
            var item = OrgPositionOperation.NewChild();
            this.Add(item);
            return item;
        }

        #endregion

        #region  Data Access

        private void Child_Fetch(OrgPosition parent)
        {

            RaiseListChangedEvents = false;

            using (var db = DBHelper.CreateDb(ConnectionStringNames.OpenExpressApp))
            {
                IQuery q = db.Query();
                q.Constrain("OrgPositionId").Equal(parent.Id);
                foreach (OrgPositionOperation c in db.Select<OrgPositionOperation>(q))
                {
                    this.Add(OrgPositionOperation.GetChild(parent, c));
                }
            }

            RaiseListChangedEvents = true;
        }

        #endregion

        ///// <summary>
        ///// 本地过滤,约定方法名称为LocalFilter
        ///// </summary>
        ///// <param name="criteria"></param>
        ///// <returns></returns>
        //public LinqBindingList<OrgPositionOperation> GetList2(OrgPositionOperationCriteria criteria)
        //{
        //    var result = from operation in this
        //                 where operation.ModuleId.Equals(criteria.ModuleId)
        //                 select operation;
        //    return result as LinqBindingList<OrgPositionOperation>;
        //}

        ///// <summary>
        ///// 本地过滤,约定方法名称为LocalFilter
        ///// </summary>
        ///// <param name="criteria"></param>
        ///// <returns></returns>
        //public OrgPositionOperations GetList(OrgPositionOperationCriteria criteria)
        //{
        //    var result = new OrgPositionOperations();
        //    foreach (var operation in this.Where(o => o.ModuleId == criteria.ModuleId))
        //    {
        //        result.Add(operation);
        //    }
        //    return result;
        //}

        ///// <summary>
        ///// 采用选择操作对象模式时, 选择列表过滤后数据, 匹配LocalFilter
        ///// </summary>
        ///// <param name="criteria"></param>
        ///// <returns></returns>
        //public BoInfoOperationSelectedList GetList_Selected(OrgPositionOperationCriteria criteria)
        //{
        //    return BoInfoOperationSelectedList.GetListInPermission(criteria.BusinessObjectInfo);
        //}

        internal bool HavePermissionOnOperation(Guid businessObjectId, Guid operationId)
        {
            foreach (var item in this)
            {
                //默认都具有权限，数据库存储的为没有权限的命令
                if (item.BusinessObjectId.Equals(businessObjectId) && item.OperationId.Equals(operationId))
                    return false;
            }
            return true;
        }

        #region IUnderlyModelList Members

        public IList GetDisplayModels(IQueryObject criteria)
        {
            var orgCriteria = criteria as OrgPositionOperationCriteria;

            var result = new BoInfoOperationSelectedList();

            foreach (var bo in orgCriteria.SelectedBOs)
            {
                var subList = BoInfoOperationSelectedList.GetListInPermission(bo);
                result.AddRange(subList);
            }

            var selectionMgr = new SelectionManager(this, result, false);
            selectionMgr.DealSelection();

            return result;
        }

        public IList GetDisplayModels(BusinessBase parent)
        {
            throw new NotImplementedException("这个类直接使用导航，不使用父对象查询。");
        }

        #endregion

    }

    [Serializable]
    [Table]
    [BusinessObject("AE067A14-A0AE-48F9-A617-F00F70739041", PropertyGroup = "ObjectName"), Label("功能权限")]
    [NavigateQueryType(typeof(OrgPositionOperationCriteria), Header = "模块", NavigateQueryMode = NavigateQueryMode.Local)]
    [NotAllowNew, /*NotAllowEdit,*/ NotAllowRemove]
    public partial class OrgPositionOperation : GBusinessBase<OrgPositionOperation>, IUnderlyModel
    {
        #region  Business Methods

        private static PropertyInfo<Guid> IdProperty =
            RegisterProperty(new PropertyInfo<Guid>("Id"));
        [System.ComponentModel.DataObjectField(true, true)]
        [Column, PK]
        [EntityProperty]
        public Guid Id
        {
            get { return GetProperty(IdProperty); }
            set { SetProperty(IdProperty, value); }
        }

        [EntityProperty]
        [Label("对象名称")]
        //[ShowInList]
        public string ObjectName
        {
            get
            {
                return BusinessObjectInfo.Label;
            }
        }

        [NotUndoable, NonSerialized]
        private Operation _operation;
        public Operation Operation
        {
            get
            {
                if (_operation == null)
                    _operation = OperationList.Get(OperationId);
                return _operation;
            }
        }

        [EntityProperty]
        [Label("功能名称")]
        [ShowInList]
        public string OperationName
        {
            get
            {
                return Operation.Name;
            }
        }

        private static PropertyInfo<Guid> OrgPositionIdProperty =
         RegisterProperty(new PropertyInfo<Guid>("OrgPositionId"));
        [Column]
        [EntityProperty]
        [Lookup("OrgPosition")]
        public Guid OrgPositionId
        {
            get { return GetProperty(OrgPositionIdProperty); }
            set { SetProperty(OrgPositionIdProperty, value); }
        }
        [NotUndoable()]
        private OrgPosition _orgPosition;
        public OrgPosition OrgPosition
        {
            get { return _orgPosition; }
            set
            {
                _orgPosition = value;
                PropertyHasChanged("OrgPosition");
            }
        }

        private static PropertyInfo<Guid> OperationIdProperty = RegisterProperty(new PropertyInfo<Guid>("OperationId"));
        [Column]
        [EntityProperty]
        [Label("功能")]
        [Lookup("Operation")]
        public Guid OperationId
        {
            get { return GetProperty(OperationIdProperty); }
            set { SetProperty(OperationIdProperty, value); }
        }

        private static PropertyInfo<Guid> ModuleIdProperty = RegisterProperty(new PropertyInfo<Guid>("ModuleId"));
        [Column]
        [EntityProperty]
        public Guid ModuleId
        {
            get { return GetProperty(ModuleIdProperty); }
            set { SetProperty(ModuleIdProperty, value); }
        }

        private static PropertyInfo<Guid> BusinessObjectIdProperty = RegisterProperty(new PropertyInfo<Guid>("BusinessObjectId"));
        [Column]
        [EntityProperty]
        [Lookup("BusinessObjectInfo")]
        public Guid BusinessObjectId
        {
            get { return GetProperty(BusinessObjectIdProperty); }
            set { SetProperty(BusinessObjectIdProperty, value); }
        }

        [NotUndoable, NonSerialized]
        private BusinessObjectInfo _businessObjectInfo;
        public BusinessObjectInfo BusinessObjectInfo
        {
            get
            {
                if (_businessObjectInfo == null)
                    _businessObjectInfo = ApplicationModel.GetBusinessObjectInfo(BusinessObjectId);
                return _businessObjectInfo;
            }
        }

        #endregion

        #region  Factory Methods

        public static OrgPositionOperation NewChild()
        {
            return DataPortal.CreateChild<OrgPositionOperation>();
        }

        public static OrgPositionOperation GetChild(OrgPosition OrgPosition, OrgPositionOperation c)
        {
            c.OrgPosition = OrgPosition;
            return DataPortal.FetchChild<OrgPositionOperation>(c);
        }

        private OrgPositionOperation()
        {
            /* require use of factory methods */
        }


        #endregion

        #region  Data Access

        protected override void Child_Create()
        {
            LoadProperty(IdProperty, Guid.NewGuid());
            ValidationRules.CheckRules();
        }

        private void Child_Fetch(OrgPositionOperation data)
        {
            LoadProperty(IdProperty, data.ReadProperty(IdProperty));
            LoadProperty(OrgPositionIdProperty, data.ReadProperty(OrgPositionIdProperty));

            Debug.Assert(null != data.OperationId);
            LoadProperty(OperationIdProperty, data.OperationId);

            LoadProperty(ModuleIdProperty, data.ModuleId);
            LoadProperty(BusinessObjectIdProperty, data.BusinessObjectId);
        }

        private void Child_Insert(BusinessBase parent)
        {
            using (var db = DBHelper.CreateDb(ConnectionStringNames.OpenExpressApp))
            {
                db.Insert(this);
                FieldManager.UpdateChildren(this);
            }
        }

        private void Child_Update(BusinessBase parent)
        {
            using (var db = DBHelper.CreateDb(ConnectionStringNames.OpenExpressApp))
            {
                db.Update(this);
                FieldManager.UpdateChildren(this);
            }
        }

        private void Child_DeleteSelf(BusinessBase parent)
        {
            using (var db = DBHelper.CreateDb(ConnectionStringNames.OpenExpressApp))
            {
                db.Delete(this);
                FieldManager.UpdateChildren(this);
            }
        }

        #endregion

        #region IUnderlyModel Members

        /// <summary>
        /// do nothing
        /// </summary>
        /// <param name="diaplayModel"></param>
        public void SetValues(IDisplayModel displayModel)
        {
            var model = displayModel as BoInfoOperationSelected;
            Debug.Assert(model != null, "model != null");

            var list = this.Parent as OrgPositionOperations;
            Debug.Assert(list != null && list.Count > 0, "list != null && list.Count > 0");
            var first = list[0];
            this.OrgPositionId = first.OrgPositionId;
            this.OrgPosition = first.OrgPosition;

            this.OperationId = model.OperationId;
            this.BusinessObjectId = model.BusinessObjectId;
        }

        public bool IsMappingTo(IDisplayModel displayModel)
        {
            var model = displayModel as BoInfoOperationSelected;
            Debug.Assert(model != null, "model != null");

            return this.OperationId == model.OperationId &&
                this.BusinessObjectId == model.BusinessObjectId;
        }

        #endregion
    }
}